import _extends from "@babel/runtime/helpers/extends";
import _asyncToGenerator from "@babel/runtime/helpers/asyncToGenerator";
import _regeneratorRuntime from "@babel/runtime/regenerator";
import './CodeGenActionBtn.scss';
import React, { useState } from 'react';
import * as CodeGenerator from '@alilc/lowcode-code-generator/standalone-loader';
import { TransformStage } from '@alilc/lowcode-types';
import { Button, Drawer, Loading, Message } from '@alifd/next';
import coerce from 'semver/functions/coerce';
import { CodeGenResult } from '@alilc/lowcode-plugin-code-generator/es/components/CodeGenResult';

export const workerJsUrl = "https://fastly.jsdelivr.net/npm/@alilc/lowcode-code-generator@1.1.5/dist/standalone-worker.min.js";

export function CodeGenActionBtn(_ref) {
  var ctx = _ref.ctx;

  var _useState = useState({
    visible: false,
    hasError: false,
    error: null,
    loading: false,
    result: null,
    schema: null,
    originalSchema: null
  }),
      state = _useState[0],
      setState = _useState[1];

  var handleClick = /*#__PURE__*/function () {
    var _ref2 = _asyncToGenerator( /*#__PURE__*/_regeneratorRuntime.mark(function _callee() {
      var originalSchema, schema, result;
      return _regeneratorRuntime.wrap(function _callee$(_context) {
        while (1) {
          switch (_context.prev = _context.next) {
            case 0:
              _context.prev = 0;
              // 打开基于 Gravity 的编辑器/出码预览器
              setState(function (prev) {
                return _extends({}, prev, {
                  loading: true,
                  visible: true,
                  hasError: false
                });
              }); // 获取 schema，并修正

              _context.next = 4;
              return ctx.project.exportSchema(TransformStage.Save);

            case 4:
              originalSchema = _context.sent;
              _context.next = 7;
              return fixSchema(originalSchema);

            case 7:
              schema = _context.sent;
              console.log('got schema: ', schema);
              setState(function (prev) {
                return _extends({}, prev, {
                  schema: schema,
                  originalSchema: originalSchema
                });
              }); // 出码...

              _context.next = 12;
              return CodeGenerator.generateCode({
                solution: 'icejs',
                schema: schema,
                flattenResult: true,
                workerJsUrl
              });

            case 12:
              result = _context.sent;
              console.log('generated: ', result);
              setState(function (prev) {
                return _extends({}, prev, {
                  loading: false,
                  result: result
                });
              });
              _context.next = 21;
              break;

            case 17:
              _context.prev = 17;
              _context.t0 = _context["catch"](0);
              console.error('failed to run code generator: ', _context.t0);
              setState(function (prev) {
                return _extends({}, prev, {
                  hasError: true,
                  error: _context.t0 instanceof Error ? _context.t0 : new Error("" + ((_context.t0 === null || _context.t0 === void 0 ? void 0 : _context.t0.message) || _context.t0))
                });
              });

            case 21:
            case "end":
              return _context.stop();
          }
        }
      }, _callee, null, [[0, 17]]);
    }));

    return function handleClick() {
      return _ref2.apply(this, arguments);
    };
  }();

  return /*#__PURE__*/React.createElement(React.Fragment, null, /*#__PURE__*/React.createElement(Button, {
    type: "primary",
    onClick: handleClick
  }, "\u51FA\u7801"), /*#__PURE__*/React.createElement(Drawer, {
    visible: state.visible,
    title: "\u51FA\u7801\u7ED3\u679C",
    width: "95vw",
    onClose: function onClose() {
      setState(function (prev) {
        return _extends({}, prev, {
          visible: false
        });
      });
    }
  }, /*#__PURE__*/React.createElement("div", {
    className: "code-gen-plugin-result"
  }, function () {
    if (state.hasError) {
      var _state$error;

      return /*#__PURE__*/React.createElement(Message, {
        type: "error",
        title: "\u51FA\u9519\u4E86"
      }, (_state$error = state.error) === null || _state$error === void 0 ? void 0 : _state$error.message);
    }

    if (state.loading) {
      return /*#__PURE__*/React.createElement(Loading, {
        className: "code-gen-plugin-loading",
        tip: "\u6B63\u5728\u51FA\u7801..."
      });
    }

    return /*#__PURE__*/React.createElement(CodeGenResult, {
      result: state.result,
      schema: state.schema,
      originalSchema: state.originalSchema
    });
  }())));
}
export function fixSchema(_x) {
  return _fixSchema.apply(this, arguments);
}

function _fixSchema() {
  _fixSchema = _asyncToGenerator( /*#__PURE__*/_regeneratorRuntime.mark(function _callee2(schema) {
    return _regeneratorRuntime.wrap(function _callee2$(_context2) {
      while (1) {
        switch (_context2.prev = _context2.next) {
          case 0:
            return _context2.abrupt("return", deepClone(_extends({}, schema, {
              componentsMap: schema.componentsMap.filter(function (c) {
                return c["package"];
              }) // 去掉没有 package 的组件
              .map(function (c) {
                // 修正版本号（对于没有有效版本号的组件，默认使用 latest）
                if (!isValidVersion(c.version)) {
                  console.warn('[WARN] got invalid version "%o" for component "%s", use "latest" as fallback', c.version, c);
                  return _extends({}, c, {
                    version: 'latest'
                  });
                } // 修正 @alifd/pro-layout 的版本
                // -- 这个包没有 ^0.1.0 的版本，这里暂且替换下


                // 修正 @alifd/pro-layout 的版本
                // -- 这个包没有 ^0.1.0 的版本，这里暂且替换下
                if (c["package"] === '@alifd/pro-layout' && c.version === '^0.1.0') {
                  console.warn('[WARN] got invalid version "%o" for "@alifd/pro-layout"! use "latest" as fallback', c.version);
                  return _extends({}, c, {
                    version: 'latest'
                  });
                }

                return c;
              })
            })));

          case 1:
          case "end":
            return _context2.stop();
        }
      }
    }, _callee2);
  }));
  return _fixSchema.apply(this, arguments);
}

function deepClone(x) {
  try {
    return JSON.parse(JSON.stringify(x));
  } catch (e) {
    throw new Error("failed to clone schema -- " + e);
  }
}

function isValidVersion(version) {
  if (!version) {
    return false;
  } // 对于一些明显非法的版本号过滤下


  if (version === '{{version}}' || version === 'null' || version === 'undefined') {
    return false;
  } // 对于 latest/beta/rc 这样的 tag 版本号要支持下


  if (/^[a-z][a-z0-9]+([a-z0-9-]+)?$/i.test(version)) {
    return true;
  } // 最后支持下所有 semver 能识别的版本


  return coerce(version) !== null;
}